package in

import (
	"errors"
	"fmt"
	"log"
	"strings"

	sql "gitee.com/dark.H/SqlParser/sql"
)

type SqlFileBottle struct {
	Bottle
	TableName string
}

func NewSqlFileBottle(infoSchema string) (bottle *SqlFileBottle, err error) {
	if !strings.HasPrefix(infoSchema, "sql://") {
		err = errors.New("not valid infoSchemal" + infoSchema)
		return
	}
	// log.Fatal("sqlfile ->", infoSchema)
	bottle = new(SqlFileBottle)
	bottle.Data = infoSchema
	bottle.Engine = strings.SplitN(infoSchema, "sql://", 2)[1]
	bottle.IsFile = true
	bottle.IsDB = true
	bottle.Tp = "SqlFile"
	return
}

func (bottle *SqlFileBottle) GetName() string {
	return bottle.Data
}

func (mdb *SqlFileBottle) GetTp() string {
	return mdb.Tp
}

func (bottle *SqlFileBottle) Desc(oper *Oper) (keys S) {
	tableName := oper.Name
	sqlParser, err := sql.LoadSql(bottle.Engine.(string))
	if err != nil {
		log.Fatal(err)
	}
	if tableName == "" {
		keys = S(sqlParser.GetTables())
	} else {
		keys = S(sqlParser.GetKeys(tableName))
	}

	return
}

func (bottle *SqlFileBottle) Query(oper *Oper) (datas Datas) {
	tableName := oper.Name
	sqlParser, err := sql.LoadSql(bottle.Engine.(string))
	if err != nil {
		log.Fatal("Load sql file err:", err)
	}

	if sqlParser.State != sql.PARSE_OK {
		if tableName != "" {
			sqlParser.SetFilterTable(tableName)
		}
		sqlParser.ParserLeft()
	}
	sqlg := make(sql.G)
	for k, v := range oper.Filter {
		sqlg[k] = fmt.Sprint(v)
	}
	log.Println("Sql state:", sqlParser.State, " fileter: ", sqlg)
	datasq := sqlParser.Datas.Query(tableName, sqlg, oper.Page, oper.Len)
	for _, v := range datasq {
		datas = append(datas, G(v))
	}
	// if !bottle.NoCached {
	SaveInCache(bottle.Data+"/"+oper.Name, datas)
	// }
	return
}
